import useFormInput, {
  MFormInputProps,
  useConfirmedFormInput,
  MConfirmedFormInputProps,
} from '../hook/useFormInput';
import {
  Input,
  Form,
  Button,
  Switch,
  Space,
  Select,
  Row,
  Col,
  Divider,
  Tooltip,
  Badge,
  Checkbox,
} from 'antd';
import React, { useState, useEffect } from 'react';

function MInput(
  props: MFormInputProps<string> & {
    without?: InstanceType<typeof RegExp>;
  }
) {
  const { without, value: originalValue, onChange } = props;
  const [value, setValue] = useFormInput(
    {
      ...props,
    },
    props
  );
  useEffect(() => {
    if (
      originalValue != null &&
      without != null &&
      without.test(originalValue)
    ) {
      onChange && onChange(originalValue.replace(without, ''));
    }
  }, [onChange, originalValue, without]);
  return (
    <Input
      type='text'
      value={value}
      onChange={(e) => {
        setValue(e.target.value);
      }}
      style={{
        width: '200px',
      }}
      allowClear
    />
  );
}
const data = [
  { id: '1', name: '123' },
  { id: '2', name: '456' },
  { id: '3', name: 'abc' },
  { id: '4', name: 'def' },
];
function MInput2(props: MFormInputProps<{ id: string; name: string }>) {
  const [value, setValue] = useFormInput(props, props);
  const targetData = data.find((x) => x.id === value?.id);
  useEffect(() => {
    if (value != null && targetData == null) {
      setValue(null);
    }
  }, [setValue, targetData, value]);
  return (
    <Select
      value={targetData?.id}
      options={data.map((x) => ({
        value: x.id,
        label: x.name,
      }))}
      onChange={(id) => {
        setValue(data.find((x) => x.id === id) || null);
      }}
      allowClear
      style={{
        width: '200px',
      }}
    ></Select>
  );
}
function MInput3(props: MConfirmedFormInputProps<string>) {
  const [
    value,
    setValue,
    handleConfirm,
    handleReset,
    // eslint-disable-next-line @typescript-eslint/no-unused-vars
    { isControlled, isModified, name },
  ] = useConfirmedFormInput(props, props);
  // console.log(name, value, props.value);
  return (
    <Input.Group>
      <Input
        type='text'
        value={value}
        onChange={(e) => {
          setValue(e.target.value);
        }}
        style={{
          width: '200px',
        }}
      ></Input>
      <Button onClick={handleReset} disabled={!isControlled}>
        重置
      </Button>
      <Badge dot={isModified}>
        <Button onClick={handleConfirm} type='primary'>
          确定
        </Button>
      </Badge>
    </Input.Group>
  );
}
function MInput4(props: MFormInputProps<string>) {
  const [value, setValue, { isControlled }] = useFormInput(props, {
    ...props,
    isComponentControlled: ({ value }) => {
      return value != null && value.includes('a');
    },
  });
  return (
    <Input.Group>
      <Input
        type='text'
        value={value}
        onChange={(e) => {
          setValue(e.target.value);
        }}
        placeholder='enter a to become uncontrolled input'
        style={{
          width: '300px',
        }}
        allowClear
      />
      <div>
        <Checkbox disabled checked={isControlled}>
          受控组件
        </Checkbox>
      </div>
    </Input.Group>
  );
}

export default function FormItemExample() {
  const [preserve, setPreserve] = useState(false);
  const [controlled, setControlled] = useState<boolean>(false);
  const [form] = Form.useForm();
  // @ts-ignore
  window.form = form;
  return (
    <Form
      form={form}
      layout='horizontal'
      labelCol={{
        span: 6,
      }}
      initialValues={{
        input0: 'ab6c',
        input1: null,
        input2: 'abc',
      }}
      onFinish={console.log.bind(console)}
    >
      <Form.Item label='input0 with never has abc'>
        <Space
          size={12}
          style={{
            verticalAlign: 'middle',
          }}
        >
          <Form.Item noStyle name={'input0'}>
            <MInput without={/abc/} />
          </Form.Item>
        </Space>
      </Form.Item>
      <Form.Item label='form input1' name='input1'>
        <MInput2 />
      </Form.Item>
      <Form.Item label='input2 with confirm' name='input2'>
        <MInput3 />
      </Form.Item>
      <Form.Item label='input2 with confirm & preserve' name='input2'>
        <MInput3 preserve />
      </Form.Item>
      <Form.Item label='input2 with confirm & preserveChange' name='input2'>
        <MInput3 preserveChange />
      </Form.Item>

      <Divider />
      <Form.Item shouldUpdate label='ttt'>
        {(form) => {
          return (
            <>
              <Button htmlType='submit'>输出到控制台</Button>
              {JSON.stringify(form.getFieldsValue(), null, 2)}
            </>
          );
        }}
      </Form.Item>
      <Divider />
      <Form.Item label='单独使用'>
        <Space
          direction='vertical'
          size={4}
          style={{
            verticalAlign: 'middle',
          }}
        >
          <Row gutter={[4, 4]}>
            <Col span={24}>
              <Space size={4}>
                <Switch
                  checked={controlled}
                  onChange={setControlled}
                  checkedChildren='受控组件'
                  unCheckedChildren='非受控组件'
                ></Switch>
                <Tooltip title='组件变为非受控状态变化时'>
                  <Switch
                    checked={preserve}
                    onChange={setPreserve}
                    checkedChildren='保持'
                    unCheckedChildren='使用默认值'
                  ></Switch>
                </Tooltip>
              </Space>
            </Col>
            <Col flex='auto'></Col>
            <Col span={24}>
              <MInput
                value={controlled ? 'controlled' : undefined}
                onChange={(value) =>
                  console.log('uncontrolled input1 changed', value)
                }
                preserve={preserve}
                defaultValue={'hello'}
              />
            </Col>
            <Col span={24}>
              <MInput
                value={controlled ? 'controlled' : undefined}
                preserve={preserve}
                defaultValue={'hello'}
              />
            </Col>

            <Col span={24}>
              <MInput2
                value={controlled ? data[0] : undefined}
                onChange={(value) =>
                  console.log('uncontrolled input3 changed', value)
                }
                preserve={preserve}
                defaultValue={data[1]}
              />
            </Col>
            <Col span={24}>
              <MInput3
                value={controlled ? 'controlled' : undefined}
                onChange={(value) =>
                  console.log('uncontrolled input4 changed', value)
                }
                preserveChange={false}
                preserve={preserve}
                defaultValue={'hello'}
              />
            </Col>
          </Row>
        </Space>
      </Form.Item>
      <Divider />
      <Form.Item label='input3 self defined controllable & preserve'>
        <Form.Item name='input3' noStyle>
          <MInput4 preserve />
        </Form.Item>
        <Button
          onClick={() =>
            form.setFieldsValue({
              input3: 'hello',
            })
          }
        >
          点击设置input3为hello
        </Button>
        <Button
          onClick={() =>
            form.setFieldsValue({
              input3: 'abc',
            })
          }
        >
          点击设置input3为abc
        </Button>
      </Form.Item>
    </Form>
  );
}
